package com.baitengsoft.patentapimonitor.api.oauth2;

import com.baitengsoft.patentapimonitor.api.entity.SysAdminUserTokenEntity;
import com.baitengsoft.patentapimonitor.api.entity.SysAdmininfoEntity;
import com.baitengsoft.patentapimonitor.api.entity.WebUserTokenEntity;
import com.baitengsoft.patentapimonitor.api.entity.WebUserinfoEntity;
import com.baitengsoft.patentapimonitor.api.service.ShiroService;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.subject.PrincipalCollection;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.util.HashSet;
import java.util.Set;

/**
 * 认证
 *
 * @author KennyGu
 * @date 2017-11-20 14:00
 */
@Component
public class OAuth2Realm extends AuthorizingRealm {

    private final  Logger log = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private ShiroService shiroService;

    @Override
    public boolean supports(AuthenticationToken token) {
        return token instanceof OAuth2Token;
    }
    /**
     * 授权(验证权限时调用)
     */
    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        // 因为非正常退出，即没有显式调用 SecurityUtils.getSubject().logout()
        // (可能是关闭浏览器，或超时)，但此时缓存依旧存在(principals)，所以会自己跑到授权方法里。
        if (!SecurityUtils.getSubject().isAuthenticated()) {
            doClearCache(principals);
            SecurityUtils.getSubject().logout();
            return null;
        }
        SysAdmininfoEntity user = (SysAdmininfoEntity)principals.getPrimaryPrincipal();
        Integer userId = user.getId();

//        //用户权限列表---预留菜单、角色动态授权用。。。。。by kenny
//        Set<String> permsSet = shiroService.getUserPermissions(userId);
        Set<String> permsSet =new HashSet<String>();


        SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
        info.setStringPermissions(permsSet);
        return info;
    }
    /**
     * 认证(登录时调用)
     */
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
        String accessToken = (String) token.getPrincipal();


        if(accessToken.startsWith("web-"))
        {
            //根据accessToken，查询用户信息
          WebUserTokenEntity webtokenEntity = shiroService.queryWebUserByToken(accessToken);
            //token失效
            if(webtokenEntity == null || webtokenEntity.getExpireTime().getTime() < System.currentTimeMillis()){
                throw new IncorrectCredentialsException("web-token失效，请重新登录");
            }

            //查询用户信息
            WebUserinfoEntity user = shiroService.queryWebUser(webtokenEntity.getUserId());
            SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(user, accessToken, getName());
            return info;
        }
        else if(accessToken.startsWith("sys-"))
        {
            //根据accessToken，查询用户信息
            SysAdminUserTokenEntity tokenEntity= shiroService.queryAdminUserByToken(accessToken);
            //token失效
            if(tokenEntity == null || tokenEntity.getExpireTime().getTime() < System.currentTimeMillis()){
                log.error("token失效");
                throw new IncorrectCredentialsException("sys-token失效，请重新登录");
            }

            //查询用户信息
            SysAdmininfoEntity user = shiroService.queryAdminUser(tokenEntity.getUserId());

            SimpleAuthenticationInfo info = new SimpleAuthenticationInfo(user, accessToken, getName());
            return info;
        }

        return null;
    }
}
